home *** CD-ROM | disk | FTP | other *** search
/ Almathera Ten Pack 3: CDPD 3 / Almathera Ten on Ten - Disc 3: CDPD3.iso / fish / 001-100 / 001-025 / 001 / dhrystone / dry.c < prev    next >
C/C++ Source or Header  |  1995-03-17  |  17KB  |  546 lines

  1. #include <stdio.h>
  2.  
  3. /*
  4.  *   "DHRYSTONE" Benchmark Program
  5.  *
  6.  *   Version:   C/1
  7.  *   Date:      12/01/84, RESULTS updated 10/22/85
  8.  *   Author:      Reinhold P. Weicker,  CACM Vol 27, No 10, 10/84 pg. 1013
  9.  *         Translated from ADA by Rick Richardson
  10.  *         Every method to preserve ADA-likeness has been used,
  11.  *         at the expense of C-ness.
  12.  *   Compile:   cc -O dry.c -o drynr         : No registers
  13.  *         cc -O -DREG=register dry.c -o dryr   : Registers
  14.  *   Defines:   Defines are provided for old C compiler's
  15.  *         which don't have enums, and can't assign structures.
  16.  *         The time(2) function is library dependant; One is
  17.  *         provided for CI-C86.  Your compiler may be different.
  18.  *         The LOOPS define is initially set for 50000 loops.
  19.  *         If you have a machine with large integers and is
  20.  *         very fast, please change this number to 500000 to
  21.  *         get better accuracy.  Please select the way to
  22.  *         measure the execution time using the TIME define.
  23.  *         For single user machines, time(2) is adequate. For
  24.  *         multi-user machines where you cannot get single-user
  25.  *         access, use the times(2) function.  If you have
  26.  *         neither, use a stopwatch in the dead of night.
  27.  *         Use a "printf" at the point marked "start timer"
  28.  *         to begin your timings. DO NOT use the UNIX "time(1)"
  29.  *         command, as this will measure the total time to
  30.  *         run this program, which will (erroneously) include
  31.  *         the time to malloc(3) storage and to compute the
  32.  *         time it takes to do nothing.
  33.  *   Run:      drynr; dryr
  34.  *
  35.  *   Results:   If you get any new machine/OS results, please send to:
  36.  *         {ihnp4,vax135,..}!houxm!vaximile!rer
  37.  *         and thanks to all that do.  Space prevents listing
  38.  *         the names of those who have provided some of these
  39.  *         results.
  40.  *   Note:      I order the list in increasing performance of the
  41.  *         "with registers" benchmark.  If the compiler doesn't
  42.  *         provide register variables, then the benchmark
  43.  *         is the same for both REG and NOREG.  I'm not going
  44.  *         to list a compiler in a better place because if it
  45.  *         had register variables it might do better. No
  46.  *         register variables is a big loss in my book.
  47.  *   PLEASE:      Send complete information about the machine type,
  48.  *         clock speed, OS and C manufacturer/version.  If
  49.  *         the machine is modified, tell me what was done.
  50.  *         Otherwise, I won't include it in this list.  My
  51.  *         favorite flame on this subject was a machine that
  52.  *         was listed as an IBM PC/XT 8086-9.54Mhz.  That must
  53.  *         have been some kind of co-processor board that ran
  54.  *         the benchmark, not the XT.  Tell me what it was!
  55.  *
  56.  * MACHINE   MICROPROCESSOR   OPERATING   COMPILER   DHRYSTONES/SEC.
  57.  * TYPE            SYSTEM            NO REG   REGS
  58.  * --------------------------   ------------   -----------   ---------------
  59.  * IBM PC/XT   8088-4.77Mhz   PC/IX      cc       257    287
  60.  * Cosmos   68000-8Mhz   UniSoft      cc       305    322
  61.  * IBM PC/XT   8088-4.77Mhz   VENIX/86 2.0   cc       297    324
  62.  * IBM PC   8088-4.77Mhz   MSDOS 2.0   b16cc 2.0    310    340
  63.  * IBM PC   8088-4.77Mhz   MSDOS 2.0   CI-C86 2.20M    390    390
  64.  * IBM PC/XT   8088-4.77Mhz   PCDOS 2.1   Lattice 2.15    403     -  @
  65.  * PDP-11/34   -      UNIX V7M   cc       387    438
  66.  * Onyx C8002   Z8000-4Mhz   IS/1 1.1 (V7)   cc       476    511
  67.  * ATT PC6300   8086-8Mhz   MSDOS 2.11   b16cc 2.0    632    684
  68.  * IBM PC/AT   80286-6Mhz   PCDOS 3.0   CI-C86 2.1    666    684
  69.  * Macintosh   68000-7.8Mhz 2M   Mac Rom      Mac C 32 bit int 694    704
  70.  * Macintosh   68000-7.7Mhz   -      MegaMax C 2.0    661    709
  71.  * NEC PC9801F   8086-8Mhz   PCDOS 2.11   Lattice 2.15    768     -  @
  72.  * ATT PC6300   8086-8Mhz   MSDOS 2.11   CI-C86 2.20M    769    769
  73.  * ATT 3B2/300   WE32000-?Mhz   UNIX 5.0.2   cc       735    806
  74.  * IBM PC/AT   80286-6Mhz   PCDOS 3.0   MS 3.0(large)    833    847 LM
  75.  * VAX 11/750   -      Unix 4.2bsd   cc       862    877
  76.  * Fast Mac   68000-7.7Mhz   -      MegaMax C 2.0    839    904 +
  77.  * Macintosh   68000-7.8Mhz 2M   Mac Rom      Mac C 16 bit int 877    909 S
  78.  * IRIS-1400   68010-10Mhz   Unix System V   cc       909   1000
  79.  * IBM PC/AT   80286-6Mhz   VENIX/86 2.1   cc       961   1000
  80.  * IBM PC/AT   80286-6Mhz   PCDOS 3.0   b16cc 2.0    943   1063
  81.  * IBM PC/AT   80286-6Mhz   PCDOS 3.0   MS 3.0(small)   1063   1086
  82.  * VAX 11/750   -      VMS      VAX-11 C 2.0    958   1091
  83.  * ATT PC7300   68010-10Mhz   UNIX 5.2   cc      1041   1111
  84.  * ATT PC6300+   80286-6Mhz   MSDOS 3.1   b16cc 2.0   1111   1219
  85.  * Sun2/120   68010-10Mhz   Sun 4.2BSD   cc      1136   1219
  86.  * IBM PC/AT   80286-6Mhz   PCDOS 3.0   CI-C86 2.20M   1219   1219
  87.  * MASSCOMP 500   68010-10MHz   RTU V3.0   cc (V3.2)   1156   1238
  88.  * Cyb DataMate   68010-12.5Mhz   Uniplus 5.0   Unisoft cc   1162   1250
  89.  * PDP 11/70   -      UNIX 5.2   cc      1162   1250
  90.  * IBM PC/AT   80286-6Mhz   PCDOS 3.1   Lattice 2.15   1250     -  @
  91.  * IBM PC/AT   80286-7.5Mhz   VENIX/86 2.1   cc      1190   1315 *
  92.  * Sun2/120   68010-10Mhz   Standalone   cc      1219   1315
  93.  * ATT 3B2/400   WE32100-?Mhz   UNIX 5.2   cc      1315   1315
  94.  * HP-110   8086-5.33Mhz   MSDOS 2.11   Aztec-C      1282   1351 ?
  95.  * IBM PC/AT   80286-6Mhz   ?      ?      1250   1388 ?
  96.  * ATT PC6300+   80286-6Mhz   MSDOS 3.1   CI-C86 2.20M   1428   1428
  97.  * Cyb DataMate   68010-12.5Mhz   Uniplus 5.0   Unisoft cc   1470   1562 S
  98.  * VAX 11/780   -      UNIX 5.2   cc      1515   1562
  99.  * MicroVAX-II   -      -      -      1562   1612
  100.  * ATT 3B20   -      UNIX 5.2   cc      1515   1724
  101.  * HP9000-500   B series CPU   HP-UX 4.02   cc      1724   -
  102.  * IBM PC/STD   80286-8Mhz   ?      ?      1724   1785
  103.  * Gould PN6005   -      UTX 1.1(4.2BSD)   cc      1675   1964
  104.  * VAX 11/785   -      UNIX 5.2   cc      2083   2083
  105.  * VAX 11/785   -      VMS      VAX-11 C 2.0   2083   2083
  106.  * Pyramid 90x   -      OSx 2.3      cc      2272   2272
  107.  * Pyramid 90x   -      OSx 2.5      cc      3125   3125
  108.  * SUN 3/75   68020-16.67Mhz   SUN 4.2 V3   cc      3333   3571
  109.  * Sun 3/180   68020-16.67Mhz   Sun 4.2      cc      3333   3846
  110.  * MC 5400   68020-16.67MHz   RTU V3.0   cc (V4.0)   3952   4054
  111.  * SUN-3/160C   68020-16.67Mhz   Sun3.0ALPHA1 Un*x      3333   4166
  112.  * Gould PN9080   -      UTX-32 1.1c   cc      -   4629
  113.  * MC 5600/5700   68020-16.67MHz   RTU V3.0   cc (V4.0)   4504   4746 %
  114.  * VAX 8600   -      VMS      VAX-11 C 2.0   7142   7142
  115.  * Amdahl 470 V/8       ?      ?      -      15015
  116.  * Amdahl 580   -      UTS 5.0 Rel 1.2   cc Ver. 1.5    23076   23076
  117.  * Amdahl 5860          ?      ?      -      28355
  118.  *
  119.  *   *  15Mhz crystal substituted for original 12Mhz;
  120.  *   +  This Macintosh was upgraded from 128K to 512K in such a way that
  121.  *      the new 384K of memory is not slowed down by video generator accesses.
  122.  *   %  Single processor; MC == MASSCOMP
  123.  *   &  Seattle Telecom STD-286 board
  124.  *   @  vanilla Lattice compiler used with MicroPro standard library
  125.  *   S  Shorts used instead of ints
  126.  *   LM Large Memory Model. (Otherwise, all 80x8x results are small model)
  127.  *   ?  I don't trust results marked with '?'.  These were sent to me with
  128.  *      either incomplete information, or with times that just don't make sense.
  129.  *      If anybody can confirm these figures, please respond.
  130.  *
  131.  **************************************************************************
  132.  *
  133.  *   The following program contains statements of a high-level programming
  134.  *   language (C) in a distribution considered representative:
  135.  *
  136.  *   assignments         53%
  137.  *   control statements      32%
  138.  *   procedure, function calls   15%
  139.  *
  140.  *   100 statements are dynamically executed.  The program is balanced with
  141.  *   respect to the three aspects:
  142.  *      - statement type
  143.  *      - operand type (for simple data types)
  144.  *      - operand access
  145.  *         operand global, local, parameter, or constant.
  146.  *
  147.  *   The combination of these three aspects is balanced only approximately.
  148.  *
  149.  *   The program does not compute anything meaningfull, but it is
  150.  *   syntactically and semantically correct.
  151.  *
  152.  */
  153.  
  154. /* Accuracy of timings and human fatigue controlled by next two lines */
  155. #define LOOPS   50000      /* Use this for slow or 16 bit machines */
  156. /*#define LOOPS   500000      /* Use this for faster machines */
  157.  
  158. /* Compiler dependent options */
  159. #define   NOENUM         /* Define if compiler has no enum's */
  160. #undef   NOSTRUCTASSIGN      /* Define if compiler can't assign structures */
  161. /* define only one of the next three defines */
  162. /*#define NOTIME      /* Define if no time() function in library */
  163. /*#define TIMES         /* Use times(2) time function */
  164. /*#define TIME         /* Use time(2) time function */
  165.  
  166. /* define the granularity of your times(2) function (when used) */
  167. #define HZ   60      /* times(2) returns 1/60 second (most) */
  168. /*#define HZ   100      /* times(2) returns 1/100 second (WECo) */
  169.  
  170.  
  171.  
  172. #ifdef   NOSTRUCTASSIGN
  173. #define   structassign(d, s)   memcpy(&(d), &(s), sizeof(d))
  174. #else
  175. #define   structassign(d, s)   d = s
  176. #endif
  177.  
  178. #ifdef   NOENUM
  179. #define   Ident1   1
  180. #define   Ident2   2
  181. #define   Ident3   3
  182. #define   Ident4   4
  183. #define   Ident5   5
  184. typedef int   Enumeration;
  185. #else
  186. typedef enum   {Ident1, Ident2, Ident3, Ident4, Ident5} Enumeration;
  187. #endif
  188.  
  189. typedef int   OneToThirty;
  190. typedef int   OneToFifty;
  191. typedef char   CapitalLetter;
  192. typedef char   String30[31];
  193. typedef int   Array1Dim[51];
  194. typedef int   Array2Dim[51][51];
  195.  
  196. struct   Record
  197. {
  198.    struct Record      *PtrComp;
  199.    Enumeration      Discr;
  200.    Enumeration      EnumComp;
  201.    OneToFifty      IntComp;
  202.    String30      StringComp;
  203. };
  204.  
  205. typedef struct Record    RecordType;
  206. typedef RecordType *   RecordPtr;
  207. typedef int      boolean;
  208.  
  209. #define   NULL      0
  210. #define   TRUE      1
  211. #define   FALSE      0
  212.  
  213. #ifndef REG
  214. #define   REG
  215. #endif
  216.  
  217. extern Enumeration   Func1();
  218. extern boolean      Func2();
  219.  
  220. #ifdef TIMES
  221. #include <sys/types.h>
  222. #include <sys/times.h>
  223. #endif
  224.  
  225. main()
  226. {
  227.    Proc0();
  228. }
  229.  
  230. /*
  231.  * Package 1
  232.  */
  233. int      IntGlob;
  234. boolean      BoolGlob;
  235. char      Char1Glob;
  236. char      Char2Glob;
  237. Array1Dim   Array1Glob;
  238. Array2Dim   Array2Glob;
  239. RecordPtr   PtrGlb;
  240. RecordPtr   PtrGlbNext;
  241.  
  242. Proc0()
  243. {
  244.    OneToFifty      IntLoc1;
  245.    REG OneToFifty      IntLoc2;
  246.    OneToFifty      IntLoc3;
  247.    REG char      CharLoc;
  248.    REG char      CharIndex;
  249.    Enumeration       EnumLoc;
  250.    String30      String1Loc;
  251.    String30      String2Loc;
  252.    register unsigned int   i;
  253.  
  254. #ifdef TIME
  255.    long         time();
  256.    long         starttime;
  257.    long         benchtime;
  258.    long         nulltime;
  259.    starttime = time(0);
  260.    for (i = 0; i < LOOPS; ++i);
  261.    nulltime = time(0) - starttime; /* Computes overhead of looping */
  262. #endif
  263. #ifdef TIMES
  264.    time_t         starttime;
  265.    time_t         benchtime;
  266.    time_t         nulltime;
  267.    struct tms      tms;
  268.    times(&tms); starttime = tms.tms_utime;
  269.    for (i = 0; i < LOOPS; ++i);
  270.    times(&tms);
  271.    nulltime = tms.tms_utime - starttime; /* Computes overhead of looping */
  272. #endif
  273.  
  274.    PtrGlbNext = (RecordPtr) malloc(sizeof(RecordType));
  275.    PtrGlb = (RecordPtr) malloc(sizeof(RecordType));
  276.    PtrGlb->PtrComp = PtrGlbNext;
  277.    PtrGlb->Discr = Ident1;
  278.    PtrGlb->EnumComp = Ident3;
  279.    PtrGlb->IntComp = 40;
  280.    strcpy(PtrGlb->StringComp, "DHRYSTONE PROGRAM, SOME STRING");
  281.  
  282. /*****************
  283. -- Start Timer --
  284. *****************/
  285.    printf ("Start timer!\n");
  286.    fflush (stdout);
  287. #ifdef TIME
  288.    starttime = time(0);
  289. #endif
  290. #ifdef TIMES
  291.    times(&tms); starttime = tms.tms_utime;
  292. #endif
  293. for (i = 0; i < LOOPS; ++i)
  294. {
  295.  
  296.    Proc5();
  297.    Proc4();
  298.    IntLoc1 = 2;
  299.    IntLoc2 = 3;
  300.    strcpy(String2Loc, "DHRYSTONE PROGRAM, 2'ND STRING");
  301.    EnumLoc = Ident2;
  302.    BoolGlob = ! Func2(String1Loc, String2Loc);
  303.    while (IntLoc1 < IntLoc2)
  304.    {
  305.       IntLoc3 = 5 * IntLoc1 - IntLoc2;
  306.       Proc7(IntLoc1, IntLoc2, &IntLoc3);
  307.       ++IntLoc1;
  308.    }
  309.    Proc8(Array1Glob, Array2Glob, IntLoc1, IntLoc3);
  310.    Proc1(PtrGlb);
  311.    for (CharIndex = 'A'; CharIndex <= Char2Glob; ++CharIndex)
  312.       if (EnumLoc == Func1(CharIndex, 'C'))
  313.          Proc6(Ident1, &EnumLoc);
  314.    IntLoc3 = IntLoc2 * IntLoc1;
  315.    IntLoc2 = IntLoc3 / IntLoc1;
  316.    IntLoc2 = 7 * (IntLoc3 - IntLoc2) - IntLoc1;
  317.    Proc2(&IntLoc1);
  318.  
  319. /*****************
  320. -- Stop Timer --
  321. *****************/
  322. }
  323.    printf ("Stop timer!\n");
  324.    fflush (stdout);
  325. #ifdef TIME
  326. benchtime = time(0) - starttime - nulltime;
  327. printf("Dhrystone time for %ld passes = %ld\n", (long) LOOPS, benchtime);
  328. printf("This machine benchmarks at %ld dhrystones/second\n",
  329.    ((long) LOOPS) / benchtime);
  330. #endif
  331. #ifdef TIMES
  332.    times(&tms);
  333.    benchtime = tms.tms_utime - starttime - nulltime;
  334. printf("Dhrystone time for %ld passes = %ld\n", (long) LOOPS, benchtime/HZ);
  335. printf("This machine benchmarks at %ld dhrystones/second\n",
  336.    ((long) LOOPS) * HZ / benchtime);
  337. #endif
  338.  
  339. }
  340.  
  341. Proc1(PtrParIn)
  342. REG RecordPtr   PtrParIn;
  343. {
  344. #define   NextRecord   (*(PtrParIn->PtrComp))
  345.  
  346.    structassign(NextRecord, *PtrGlb);
  347.    PtrParIn->IntComp = 5;
  348.    NextRecord.IntComp = PtrParIn->IntComp;
  349.    NextRecord.PtrComp = PtrParIn->PtrComp;
  350.    Proc3(NextRecord.PtrComp);
  351.    if (NextRecord.Discr == Ident1)
  352.    {
  353.       NextRecord.IntComp = 6;
  354.       Proc6(PtrParIn->EnumComp, &NextRecord.EnumComp);
  355.       NextRecord.PtrComp = PtrGlb->PtrComp;
  356.       Proc7(NextRecord.IntComp, 10, &NextRecord.IntComp);
  357.    }
  358.    else
  359.       structassign(*PtrParIn, NextRecord);
  360.  
  361. #undef   NextRecord
  362. }
  363.  
  364. Proc2(IntParIO)
  365. OneToFifty   *IntParIO;
  366. {
  367.    REG OneToFifty      IntLoc;
  368.    REG Enumeration      EnumLoc;
  369.  
  370.    IntLoc = *IntParIO + 10;
  371.    for(;;)
  372.    {
  373.       if (Char1Glob == 'A')
  374.       {
  375.          --IntLoc;
  376.          *IntParIO = IntLoc - IntGlob;
  377.          EnumLoc = Ident1;
  378.       }
  379.       if (EnumLoc == Ident1)
  380.          break;
  381.    }
  382. }
  383.  
  384. Proc3(PtrParOut)
  385. RecordPtr   *PtrParOut;
  386. {
  387.    if (PtrGlb != NULL)
  388.       *PtrParOut = PtrGlb->PtrComp;
  389.    else
  390.       IntGlob = 100;
  391.    Proc7(10, IntGlob, &PtrGlb->IntComp);
  392. }
  393.  
  394. Proc4()
  395. {
  396.    REG boolean   BoolLoc;
  397.  
  398.    BoolLoc = Char1Glob == 'A';
  399.    BoolLoc |= BoolGlob;
  400.    Char2Glob = 'B';
  401. }
  402.  
  403. Proc5()
  404. {
  405.    Char1Glob = 'A';
  406.    BoolGlob = FALSE;
  407. }
  408.  
  409. extern boolean Func3();
  410.  
  411. Proc6(EnumParIn, EnumParOut)
  412. REG Enumeration   EnumParIn;
  413. REG Enumeration   *EnumParOut;
  414. {
  415.    *EnumParOut = EnumParIn;
  416.    if (! Func3(EnumParIn) )
  417.       *EnumParOut = Ident4;
  418.    switch (EnumParIn)
  419.    {
  420.    case Ident1:   *EnumParOut = Ident1; break;
  421.    case Ident2:   if (IntGlob > 100) *EnumParOut = Ident1;
  422.          else *EnumParOut = Ident4;
  423.          break;
  424.    case Ident3:   *EnumParOut = Ident2; break;
  425.    case Ident4:   break;
  426.    case Ident5:   *EnumParOut = Ident3;
  427.    }
  428. }
  429.  
  430. Proc7(IntParI1, IntParI2, IntParOut)
  431. OneToFifty   IntParI1;
  432. OneToFifty   IntParI2;
  433. OneToFifty   *IntParOut;
  434. {
  435.    REG OneToFifty   IntLoc;
  436.  
  437.    IntLoc = IntParI1 + 2;
  438.    *IntParOut = IntParI2 + IntLoc;
  439. }
  440.  
  441. Proc8(Array1Par, Array2Par, IntParI1, IntParI2)
  442. Array1Dim   Array1Par;
  443. Array2Dim   Array2Par;
  444. OneToFifty   IntParI1;
  445. OneToFifty   IntParI2;
  446. {
  447.    REG OneToFifty   IntLoc;
  448.    REG OneToFifty   IntIndex;
  449.  
  450.    IntLoc = IntParI1 + 5;
  451.    Array1Par[IntLoc] = IntParI2;
  452.    Array1Par[IntLoc+1] = Array1Par[IntLoc];
  453.    Array1Par[IntLoc+30] = IntLoc;
  454.    for (IntIndex = IntLoc; IntIndex <= (IntLoc+1); ++IntIndex)
  455.       Array2Par[IntLoc][IntIndex] = IntLoc;
  456.    ++Array2Par[IntLoc][IntLoc-1];
  457.    Array2Par[IntLoc+20][IntLoc] = Array1Par[IntLoc];
  458.    IntGlob = 5;
  459. }
  460.  
  461. Enumeration Func1(CharPar1, CharPar2)
  462. CapitalLetter   CharPar1;
  463. CapitalLetter   CharPar2;
  464. {
  465.    REG CapitalLetter   CharLoc1;
  466.    REG CapitalLetter   CharLoc2;
  467.  
  468.    CharLoc1 = CharPar1;
  469.    CharLoc2 = CharLoc1;
  470.    if (CharLoc2 != CharPar2)
  471.       return (Ident1);
  472.    else
  473.       return (Ident2);
  474. }
  475.  
  476. boolean Func2(StrParI1, StrParI2)
  477. String30   StrParI1;
  478. String30   StrParI2;
  479. {
  480.    REG OneToThirty      IntLoc;
  481.    REG CapitalLetter   CharLoc;
  482.  
  483.    IntLoc = 1;
  484.    while (IntLoc <= 1)
  485.       if (Func1(StrParI1[IntLoc], StrParI2[IntLoc+1]) == Ident1)
  486.       {
  487.          CharLoc = 'A';
  488.          ++IntLoc;
  489.       }
  490.    if (CharLoc >= 'W' && CharLoc <= 'Z')
  491.       IntLoc = 7;
  492.    if (CharLoc == 'X')
  493.       return(TRUE);
  494.    else
  495.    {
  496.       if (strcmp(StrParI1, StrParI2) > 0)
  497.       {
  498.          IntLoc += 7;
  499.          return (TRUE);
  500.       }
  501.       else
  502.          return (FALSE);
  503.    }
  504. }
  505.  
  506. boolean Func3(EnumParIn)
  507. REG Enumeration   EnumParIn;
  508. {
  509.    REG Enumeration   EnumLoc;
  510.  
  511.    EnumLoc = EnumParIn;
  512.    if (EnumLoc == Ident3) return (TRUE);
  513.    return (FALSE);
  514. }
  515.  
  516. #ifdef   NOSTRUCTASSIGN
  517. memcpy(d, s, l)
  518. register char   *d;
  519. register char   *s;
  520. int   l;
  521. {
  522.    while (l--) *d++ = *s++;
  523. }
  524. #endif
  525.  
  526. /*
  527.  *   Library function for compilers with no time(2) function in the
  528.  *   library.
  529.  */
  530. #ifdef   NOTIME
  531. long   time(p)
  532. long   *p;
  533. {      /* CI-C86 time function - don't use around midnight */
  534.    long   t;
  535.    struct regval {unsigned int ax,bx,cx,dx,si,di,ds,es; } regs;
  536.  
  537.    regs.ax = 0x2c00;
  538.    sysint21(®s, ®s);
  539.    t = ((regs.cx>>8)*60L + (regs.cx & 0xff))*60L + (regs.dx>>8);
  540.    if (p) *p = t;
  541.    return t;
  542. }
  543. #endif
  544.  
  545.  
  546.